package com.excesys.exsecs.access.controller;

import cn.hutool.core.util.ArrayUtil;
import cn.hutool.core.collection.CollUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.toolkit.ObjectUtils;
import com.baomidou.mybatisplus.core.toolkit.StringUtils;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.excesys.exsecs.access.vo.AccessProductVO;
import com.excesys.exsecs.access.vo.AccessThingModelVO;
import com.excesys.exsecs.common.core.util.R;
import com.excesys.exsecs.common.excel.annotation.RequestExcel;
import com.excesys.exsecs.common.log.annotation.SysLog;
import com.excesys.exsecs.access.entity.AccessThingModel;
import com.excesys.exsecs.access.service.AccessThingModelService;
import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.databind.ObjectMapper;
import org.springframework.security.access.prepost.PreAuthorize;
import com.excesys.exsecs.common.excel.annotation.ResponseExcel;
import io.swagger.v3.oas.annotations.security.SecurityRequirement;
import org.springdoc.api.annotations.ParameterObject;
import org.springframework.http.HttpHeaders;
import io.swagger.v3.oas.annotations.tags.Tag;
import io.swagger.v3.oas.annotations.Operation;
import lombok.RequiredArgsConstructor;
import org.springframework.validation.BindingResult;
import org.springframework.web.bind.annotation.*;

import java.util.*;

/**
 * 物模型表
 *
 * @author lxc
 * @date 2024-05-06 17:44:02
 */
@RestController
@RequiredArgsConstructor
@RequestMapping("/accessThingModel" )
@Tag(description = "accessThingModel" , name = "物模型表管理" )
@SecurityRequirement(name = HttpHeaders.AUTHORIZATION)
public class AccessThingModelController {

    private final  AccessThingModelService accessThingModelService;

    /**
     * 通过productKey查询物模型
     * @param productKey productKey
     * @return R
     */
    @Operation(summary = "通过id查询" , description = "通过id查询" )
    @GetMapping("/getThingModelByProductKey" )
    @PreAuthorize("@pms.hasPermission('access_accessProduct_view')" )
    public R getThingModelByProductKey(String productKey) {
        return R.ok(accessThingModelService.getThingModelByProductKey(productKey));
    }
    /**
     * 通过productKey查询物模型Json
     * @param productKey productKey
     * @return R
     */
    @Operation(summary = "列表" , description = "列表" )
    @GetMapping("/getlistProperties" )
    public R getlistProperties(String productKey) throws JsonProcessingException {
        List<Map> list = new ArrayList();
        AccessThingModel accessThingModel  =  accessThingModelService.getBaseMapper().selectOne(Wrappers.lambdaQuery(AccessThingModel.class).eq(Objects.nonNull(productKey), AccessThingModel::getProductKey, productKey));
        if (accessThingModel != null){
           // 解析整个JSON对象
           JsonNode rootNode = new ObjectMapper().readTree(String.valueOf(accessThingModel.getModel()));
           // 定位到properties数组
           rootNode.get("properties").forEach(j -> {
               Map map = new HashMap();
               map.put("name",j.get("name").asText());
               map.put("value",j.get("identifier").asText());
               list.add(map);
           });
         }
        return R.ok(list);
    }


    /**
     * 通过productKey查询物模型JSon 执行动作
     * @param productKey productKey
     * @return R
     */
    @Operation(summary = "执行动作" , description = "执行动作" )
    @GetMapping("/getlistServices" )
    public R getlistServices(String productKey) throws JsonProcessingException {
        List<Map> list = new ArrayList();
        AccessThingModel accessThingModel  =  accessThingModelService.getBaseMapper().selectOne(Wrappers.lambdaQuery(AccessThingModel.class).eq(Objects.nonNull(productKey), AccessThingModel::getProductKey, productKey));
        if (accessThingModel != null){
            // 解析整个JSON对象
            JsonNode rootNode = new ObjectMapper().readTree(String.valueOf(accessThingModel.getModel()));
            // 定位到properties数组
            rootNode.get("services").forEach(j -> {
                Map map = new HashMap();
                map.put("name",j.get("name").asText());
                map.put("value",j.get("identifier").asText());
                // 定位到inputData数组
                j.get("inputData").forEach(k -> {
                    map.put("data",k.get("dataType").get("specs"));
                });
                list.add(map);
            });
        }
        return R.ok(list);
    }


    /**
     * 新增物模型表
     * @param accessThingModel 物模型表
     * @return R
     */
    @Operation(summary = "新增物模型表" , description = "新增物模型表" )
    @SysLog("新增物模型表" )
    @PostMapping
    @PreAuthorize("@pms.hasPermission('access_accessProduct_add')" )
    public R save(@RequestBody AccessThingModel accessThingModel) {
        return R.ok(accessThingModelService.saveModel(accessThingModel));
    }

    /**
     * 修改物模型表
     * @param accessThingModel 物模型表
     * @return R
     */
    @Operation(summary = "修改物模型表" , description = "修改物模型表" )
    @SysLog("修改物模型表" )
    @PutMapping
    @PreAuthorize("@pms.hasPermission('access_accessProduct_edit')" )
    public R updateById(@RequestBody AccessThingModel accessThingModel) {
        return R.ok(accessThingModelService.updateById(accessThingModel));
    }

    /**
     * 通过id删除物模型表
     * @param ids id列表
     * @return R
     */
    @Operation(summary = "通过id删除物模型表" , description = "通过id删除物模型表" )
    @SysLog("通过id删除物模型表" )
    @DeleteMapping
    @PreAuthorize("@pms.hasPermission('access_accessProduct_del')" )
    public R removeById(@RequestBody Long[] ids) {
        return R.ok(accessThingModelService.removeBatchByIds(CollUtil.toList(ids)));
    }

    /**
     * 导入物模型
     * @param excelVOList 产品列表
     * @param bindingResult 错误信息列表
     * @return R
     */
    @PostMapping("/import")
    //@PreAuthorize("@pms.hasPermission('access_accessDeviceInfo_export')")
    public R importAccessThingModel(@RequestExcel List<AccessThingModelVO> excelVOList, String productKey, BindingResult bindingResult) {
        if (StringUtils.isBlank(productKey)){
            return R.failed("产品为空，导入失败!");
        }
        return accessThingModelService.importProduct(excelVOList,productKey, bindingResult);
    }


    /**
     * 导出excel 表格
     * @param accessThingModel 查询条件
   	 * @param ids 导出指定ID
     * @return excel 文件流
     */
    @ResponseExcel
    @GetMapping("/export")
    @PreAuthorize("@pms.hasPermission('access_accessProduct_export')" )
    public List<AccessThingModelVO> export(AccessThingModel accessThingModel,Long[] ids) {
        return accessThingModelService.exportThingModel(accessThingModel);
    }
}